iT邦幫忙

2018 iT 邦幫忙鐵人賽
DAY 15
2
Data Technology

你都在公司都在幹啥R? R語言資料分析經驗分享系列 第 15

【15】當老闆突然又問:你畫的地點都是用經緯度座標畫的,可是我們會員資料庫存的是地址啊,你可以用地址在地圖上畫點嗎?

  • 分享至 

  • xImage
  •  

沒錯,在多數情況下,我們手上的資料都是中文地址,如果要轉變成經緯度目標需要透過一些第三方服務,這邊我們用google 提供的Geocoding API 服務來使用。

那在開始前,先安裝必要的套件,httr可以讓我們使用GET 或POST 去取得資料,json可以用於解析回傳回來的json格式。

#install.packages("httr")
#install.packages("rjson")
library(httr)
library(rjson)

而Geocoding API 使用的格式如下:
https://maps.googleapis.com/maps/api/geocode/json?language=zh-TW&address=台北火車站

可以得出經緯度json結果。
https://ithelp.ithome.com.tw/upload/images/20180101/20107299PNBUe2gzZH.png

再來,我們便可使用json 去取得經緯度資訊。

lat <- jsonResult$results[[1]]$geometry$location$lat
lng <- jsonResult$results[[1]]$geometry$location$lng

我在input 資料夾中,新增了一個測試資料集address.csv 。

https://ithelp.ithome.com.tw/upload/images/20180101/20107299WJ0Xd7rQ5m.png

回到R ,我們便可以利用前面的方法取得所有地址的經緯度座標位置,先將撈取經緯度的方法定義成function,另外有一點需要特別注意的是,因為google 的API 有限制問候的頻率,所以我在函式中多加了Sys.sleep(1) 延遲一秒,以避免被block,另外這邊犯離還蠻容易超出google限制而有錯誤,因此建議大家還是去申請API Key 比較不容易出現問題。

getLatLng <- function(address){
 
    urlData <- GET(paste0("https://maps.googleapis.com/maps/api/geocode/json?language=zh-TW&address=", URLencode(address)))
    jsonResult <- rjson::fromJSON(rawToChar(urlData$content))
    Sys.sleep(1)
    if(jsonResult$status != "OK"){
        print("Google geocode API Error")
        return("error")
    }
    print("LatLng Got")
    lat <<- jsonResult$results[[1]]$geometry$location$lat
    lng <<- jsonResult$results[[1]]$geometry$location$lng
    
    return(paste(lat, lng, sep=","))
}

然後引入資料,並使用rowwise() 函式,把每個row 獨立單程一個參數帶入剛剛定義的函式。

address_data = read.csv("input/address.csv", stringsAsFactors=FALSE, header=FALSE)

result <- address_data %>%
    rowwise() %>%
    mutate(LatLng = getLatLng(V1))

結果如下

https://ithelp.ithome.com.tw/upload/images/20180101/20107299Zrnz3vJYbR.png

然後前幾天教學我們知道separate() 可以用來切割欄位,因此我們可以這樣做。

result <- address_data %>%
    rowwise() %>%
    mutate(LatLng = getLatLng(V1)) %>%
    filter(LatLng!="error") %>%
    separate(LatLng, c("Lat", "Lng"), sep=",") %>%
    mutate(Lat=as.numeric(Lat), Lng=as.numeric(Lng))

計算結果:

https://ithelp.ithome.com.tw/upload/images/20180101/201072992m1wsp5fSp.png

最後,我們把經緯度畫在地圖上就完成囉!

ggmap(google_map) +
    geom_point(data=result, aes(x=Lng, y=Lat), colour='red')

https://ithelp.ithome.com.tw/upload/images/20180101/20107299DcGaOQaDt3.png

ref:
day15原始碼


上一篇
【14】當老闆突然問:對了,有沒有什麼辦法可以分析地址啊?可以顯示在地圖上的那種。
下一篇
【16】當老闆突然再問:很好,現在地址很明瞭了,但是我想把在附近的地址當成一組做分群,這有辦法嗎?
系列文
你都在公司都在幹啥R? R語言資料分析經驗分享30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言